(defmeth graph-proto :select-buttons (&key (vertical t) (double nil)
          (help t) (out t) (in t) (cancel t) (reset t) (hot-spot nil)) 
"Creates horizontal or vertical button bar for namelists. Arguments are VERTICAL, for whether the bar is vertical or horizontal (T by default), and HELP, IN, OUT, CANCEL, RESET, and HOT-SPOT, which determine which of the 5 buttons and the menu hot-spot appears (all T by default)."
    
  (cond
    ((not double)
     (if vertical
         (setf margin (list (+ 17 (send self :text-descent)) 0 0 0))
         (setf margin (list 0 (+ 17 (send self :text-descent)) 0 0)) ))
    (t
     (setf margin (list 0 (+ 26 (send self :text-descent)) 0 0)) ));+ 26
  (apply #'send self :margin margin)
  (when (= *color-mode* 0) (setf color nil))
  (let ((overlay 
         (first (send self :add-overlay 
                      (send selector-overlay-proto :new 
                            :vertical vertical :double double
                            :help help :remove out :focus in 
                            :cancel cancel :reset reset :hot-spot hot-spot))))
        (graph self)
        )
    (defmeth self :do-motion (x y)
      (let* ((margin (send self :margin))
             )
        (cond
          ((and (> (second margin) 0) (<= y (second margin)))
           (send self :cursor 'solid-arrow))
          ((and (> (fourth margin) 0)
                (> y (- (send self :canvas-height) (fourth margin))))
           (send self :cursor 'solid-arrow))
          ((and (> (first margin) 0) (<= x (first margin)))
           (send self :cursor 'solid-arrow))
          ((and (> (third margin) 0) 
                (> x (- (send self :canvas-width) (third margin))))
           (send self :cursor 'solid-arrow))
          (t
           (when (not (eq (send self :cursor) (send self :set-mode-cursor)))
                 (send self :cursor) (send self :set-mode-cursor))
           (send self :do-brush-motion x y)))
        overlay))
    overlay))


(defproto selector-overlay-proto 
  '(buttons help remove focus cancel reset double vertical vertical-offset button-xy-list)  
   () vista-graph-overlay-proto)

(defmeth selector-overlay-proto :isnew 
  (&key (vertical t) (double nil) (help nil) (remove t) 
        (focus t) (cancel t) (reset t) (hot-spot nil))
  (call-next-method :help help :zoom nil :mouse-mode nil 
                    :new-x nil :new-y nil :pop nil :hot-spot hot-spot)
  (send self :help help)
  (send self :remove remove)
  (send self :focus focus)
  (send self :cancel cancel)
  (send self :reset reset)
  (send self :vertical vertical)
  (send self :double double)
  (send self :hot-spot hot-spot)
  )

(defmeth selector-overlay-proto :buttons (&optional (list nil set))
"Args: (&optional logical)
Sets or returns which buttons are hilited."
  (if set (setf (slot-value 'buttons) list))
  (slot-value 'buttons))

(defmeth selector-overlay-proto :help (&optional (logical nil set))
"Args: (&optional logical)
Sets or returns whether help button is to be drawn."
  (if set (setf (slot-value 'plot-help) logical))
  (slot-value 'plot-help))

(defmeth selector-overlay-proto :remove (&optional (logical nil set))
"Args: (&optional logical)
Sets or returns whether OUT button is to be drawn."
  (if set (setf (slot-value 'remove) logical))
  (slot-value 'remove))

(defmeth selector-overlay-proto :focus (&optional (logical nil set))
"Args: (&optional logical)
Sets or returns whether IN button is to be drawn."
  (if set (setf (slot-value 'focus) logical))
  (slot-value 'focus))

(defmeth selector-overlay-proto :cancel (&optional (logical nil set))
"Args: (&optional logical)
Sets or returns whether cancel button is to be drawn."
  (if set (setf (slot-value 'cancel) logical))
  (slot-value 'cancel))

(defmeth selector-overlay-proto :reset (&optional (logical nil set))
"Args: (&optional logical)
Sets or returns whether reset button is to be drawn."
  (if set (setf (slot-value 'reset) logical))
  (slot-value 'reset))

(defmeth selector-overlay-proto :double (&optional (logical nil set))
"Args: (&optional vertical)
Sets or returns whether part of a double namelist."
  (if set (setf (slot-value 'double) logical))
  (slot-value 'double))

(defmeth selector-overlay-proto :vertical (&optional (logical nil set))
"Args: (&optional vertical)
Sets or returns whether the button bar is vertical or horizontal."
  (if set (setf (slot-value 'vertical) logical))
  (slot-value 'vertical))

(defmeth selector-overlay-proto :vertical-offset (&optional (logical nil set))
"Args: (&optional vertical)
Sets or returns the value the aligns buttons with top of vertical bar."
  (if set (setf (slot-value 'vertical-offset) logical))
  (slot-value 'vertical-offset))

(defmeth selector-overlay-proto :button-xy-list (&optional (lol nil set))
"Args: (&optional lol)
Sets or returns a list of xy coordinate lists, one for each button."
  (if set (setf (slot-value 'button-xy-list) lol))
  (slot-value 'button-xy-list))




(defmeth selector-overlay-proto :redraw ()
  (let* ((graph (slot-value 'graph))
         (draw-color (send graph :draw-color))
         (color-mode *color-mode*)
         (vr (send graph :view-rect))
         (mr (send graph :margin))
         (i 0)
         (topy 13)
         (height 10)
         (gap 2)
         (td (send graph :text-descent))
         (bottom-of-top (- (second (send graph :margin)) 3))
         (right-of-left (- (first (send graph :margin)) 3))
         (vertical (send self :vertical))
        ;(c (if (send self :double) 12 0))
         (c (if vertical 0 12))
         )
    (send graph :line-type 'solid)
    (setf vr (combine (first vr) (+ c (second vr)) (third vr) (fourth vr)))
    (when (not color-mode) (send graph :use-color nil))
    (when (or (not (send self :old-canvas-width));fwy!
              (/= (send self :old-canvas-width) ;fwy!
                  (send graph :canvas-width)));fwy!
          (send self :old-canvas-width (send graph :canvas-width));fwy!
          (send self :lefts nil));fwy!
    (when (not (send self :lefts)) (send self :setup-redraw))

    (if (and color-mode (send *vista* :background-color))
        (send graph :draw-color 'toolbar-background)
        (send graph :draw-color 'white))
    (cond 
      ((not vertical)
       (send graph :paint-rect (first vr) (+ c (second vr))
             (third vr) bottom-of-top)
       (send graph :draw-color 'black)
      ; (if (send self :double)
      ;     (send graph :draw-line (first vr) (+ (second vr) c bottom-of-top)
      ;           (+ (first vr) (third vr));(first (send graph :size))
      ;           (+ (second vr) c bottom-of-top))
      ;     (send graph :draw-line (first vr) (+ (second vr) c 4) 
      ;           (+ (first vr) (third vr)) (+ (second vr) c 4)))
       (send graph :draw-line -1 (+ (second vr) 16) (third vr) (+ (second vr) 16))
       (when (send self :double)
             (send graph :draw-line -1 (+ (second vr) -1) (third vr) (+ (second vr) -1)))
       )
      (t
       (send graph :paint-rect (first vr) (+ c (second vr))
             (+ (first vr) 1 right-of-left) (fourth vr))
       (send graph :draw-color 'black)
       (send graph :draw-line (+ (first vr) right-of-left) (+ c (second vr)) 
             (+ (first vr) right-of-left) (fourth vr))))
    (when (send self :help) 
          (setf xy  (send self :draw-button nil i :vr vr :vertical vertical))
          (setf i (1+ i)))
    
    (when (send self :focus) 
          (send self :draw-button nil i :vr vr :vertical vertical) (setf i (1+ i)))
    (when (send self :remove)   
          (send self :draw-button nil i :vr vr :vertical vertical) (setf i (1+ i)))
    
    (when (send self :cancel)  
          (send self :draw-button nil i :vr vr :vertical vertical) (setf i (1+ i)))
    (when (send self :reset) 
          (send self :draw-button nil i :vr vr :vertical vertical) (setf i (1+ i)))
    (when (and *plot-menu-hot-spot* (send self :hot-spot))
          (send self :pull-down-menu-spots t (send self :new-x) (send self :new-y)) )
    ))
  
(defmeth selector-overlay-proto :setup-redraw ()
  (let* ((graph (slot-value 'graph))
         (string (list "Help" "In" "Out" "Cancel" "None"))
         (short-string (list "?" "Y" "N" "XXX" "---"))  
         (buttons (list (send self :help) (send self :focus) (send self :remove)
                        (send self :cancel) (send self :reset)))
         (bar (send self :setup-redraw-button-bar string buttons short-string 0
                    (send self :vertical))) 
         (lefts (first bar))
         (strings (second bar))
         )
    (send self :initialize-vertical-offset strings)
    (send self :num-top-buttons (length (first bar)))
    (send self :lefts lefts)
    (send self :strings strings)
    (send self :buttons (repeat nil (length strings)))
    (when (and *plot-menu-hot-spot* (send self :hot-spot))
          (send self :pull-down-menu-spots t (send self :new-x) (send self :new-y)))
    ))

(defmeth selector-overlay-proto :pull-down-menu-spots (menu x y)
  (let* ((fake-overlay (send self :graph))
         (container (send fake-overlay :container))
         (popout? (if container (send container :pop-out) nil))
         (vr (send fake-overlay :view-rect))
         (cr (send fake-overlay :content-rect)))
    (when menu (send  self :draw-pull-down-menu 
                      (+ (first vr) (third vr) (if popout? -21 -15)) 15 2))
    ))


(defmeth selector-overlay-proto :do-click-pull-down-menu (x y)
  (let* ((fake-overlay (slot-value 'graph))
         (container (send fake-overlay :container))
         (namelist  (send container :namelist))
         (popout? (if container (send container :pop-out) nil))
         (vr (send fake-overlay :view-rect))
         (cr (send fake-overlay :content-rect))
         (menux (+ (first vr) (third vr) (if popout? -21 -15)))
         (menuy 15)
         )
    (when (and (< menux x (+ menux 8)) (< menuy y (+ menuy 8)))
          (setf result (send (send namelist :menu) :popup x y fake-overlay)))
    ))

(defmeth selector-overlay-proto :initialize-vertical-offset (strings)
  (let* ((big-string "")
         (knt (length strings))
         )
    (dotimes (i knt)
              (setf big-string (strcat big-string (select strings i))))
    (send self :vertical-offset 
          (+ (* knt 15)
             (send (slot-value 'graph) :text-width big-string)))))


(defmeth selector-overlay-proto :do-click (x y m1 m2)
  (let* ((graph (slot-value 'graph))
         (lefts (copy-list (send self :lefts)))
         (height 10)
         (width  10)
         (gap 2)
         (topx 10)
         ;(topy (if (send self :double) 15 3))
         (vertical (send self :vertical))
         (topy (if vertical 3 15))
         (bottom (+ topy height gap))
         (idling (select (copy-list (list (send graph :idle-on))) 0))
         (i 0)
         )
(print "NAMEOVRL.lsp DO-CLICK for selector-overlay-proto")
    (when vertical
          (setf lefts (- (send self :vertical-offset) lefts))
          (setf temp y)
          (setf y x)
          (setf x temp)
          )
    (when (< y bottom)
          (when (and *plot-menu-hot-spot* (send self :hot-spot))
                (send self :do-click-pull-down-menu x y))

          (when (send self :help)
                (when (and (< (select lefts i) x (+ width (select lefts i)))
                           (< topy y (+ topy height)))
                      (send graph :idle-on nil)
                      (send self :draw-button t  i :y topy :vertical vertical)
                      (send graph :plot-help)
                      (pause 10)
                      (send self :draw-button nil i :y topy :vertical vertical)
                      (send graph :idle-on idling))
                (setf i (1+ i)))
          (when (send self :focus)
                (when (and (< (select lefts i) x (+ width (select lefts i)))
                           (< topy y (+ topy height)))
                      (send graph :idle-on nil)
                      (send self :draw-button t  i :y topy :vertical vertical)
                      (send graph :in)
                      (pause 10)
                      (send self :draw-button nil i :y topy :vertical vertical)
                      (send graph :idle-on idling))
                (setf i (1+ i)))
          (when (send self :remove)
                (when (and (< (select lefts i) x (+ width (select lefts i)))
                           (< topy y (+ topy height)))
                      (send graph :idle-on nil)
                      (send self :draw-button t  i :y topy :vertical vertical)
                      (send graph :out)
                      (pause 10)
                      (send self :draw-button nil  i :y topy :vertical vertical)
                      (send graph :idle-on idling))
                (setf i (1+ i)))
          
          (when (send self :cancel)
                (when (and (< (select lefts i) x (+ width (select lefts i)))
                           (< topy y (+ topy height)))
                      (send graph :idle-on nil)
                      (send self :draw-button t  i :y topy :vertical vertical)
                      (send graph :undo)
                      (pause 10)
                      (send self :draw-button nil  i :y topy :vertical vertical)
                      (send graph :idle-on idling))
                (setf i (1+ i)))
          (when (send self :reset)
                (when (and (< (select lefts i) x (+ width (select lefts i)))
                           (< topy y (+ topy height)))
                      (send graph :idle-on nil)
                      (send self :draw-button t  i :y topy :vertical vertical)
                      (send graph :reset)
                      (pause 10)
                      (send self :draw-button nil  i :y topy :vertical vertical)
                      (send graph :idle-on idling))
                (setf i (1+ i)))
          )))
